//
//  YYAddressPickerView.swift
//  DatePickerView
//
//  Created by 蓓蕾 on 2022/3/23.
//

import UIKit

class YYAddressPickerView: UIView, UIPickerViewDelegate, UIPickerViewDataSource {
    
    enum YYAddressPickerMode:Int {
        /** 显示【省市区】（默认） */
        case YYAddressPickerModeArea
        /** 显示【省市】 */
        case YYAddressPickerModeCity
        /** 显示【省】 */
        case YYAddressPickerModeProvince
    }
    
    typealias YYAddressResultBlock=(YYProvinceModel, YYCityModel, YYAreaModel)->Void
    var selectResultBlock: YYAddressResultBlock?
    
    let systemBlackColr = UIColor(hex: 0x424243)//系统常用的黑色
    let systemgrayColor = UIColor(hex: 0xb2b2b2)//系统常用的灰色
    
    var CancelReturnBlock: (() -> Void)? //取消按钮的回调
//    var SuccessReturnBlock: ((_ date:String) -> Void)?//选择的回调
    
    var bgView : UIView?
    private lazy var titleView = UILabel()
    private lazy var cancelButton = UIButton()
    private lazy var confirmButton = UIButton()
    var lineView = UIView()//一条横线
    var pickerView = UIPickerView()
    
    var BorderHeight = 400
    var PickerColumnNumber = 0
    var currentAddressPickerMode = YYAddressPickerMode.YYAddressPickerModeArea
    
    private var resultSelectDateStringValue : String!
    private var resultSelectDateValue : NSDate!
    /// 默认选中日期
    private var initialDateString = ""
    
    //数据相关
    private var addressSource = NSArray()
    private var provinceResultModel = YYProvinceModel()
    private var cityResultModel = YYCityModel()
    private var areaResultModel = YYAreaModel()
    
    
    static let shared = YYAddressPickerView()
    
    private override init(frame: CGRect) {
        super.init(frame: frame)
        print("init 方法")
        initUI()
//        initData()
    }
    
    override func copy() -> Any {
        print("copy 方法")
        return self // SingletonClass.shared
    }
    
    override func mutableCopy() -> Any {
        print("mutableCopy 方法")
        return self // SingletonClass.shared
    }
    
    func reset() {
        print("reset 方法")
    }
    
    /// 最大宽度
    var maxWidth:Double = 90000.0 {
        didSet {
            pickerView.reloadAllComponents()
        }
    }
    
    @objc private func dismiss(){
        dismissDatePickerView()
    }
    
    private func initUI(){
        let boundsSizeWidth:CGFloat = UIScreen.main.bounds.width
        let boundsSizeHeight:CGFloat = UIScreen.main.bounds.height
        self.frame = CGRect(x: 0, y: 0, width: boundsSizeWidth, height: boundsSizeHeight)
        self.backgroundColor = UIColor.white
        
        
        pickerView.frame = CGRect(x: 0, y: Int(boundsSizeHeight) - BorderHeight, width: Int(boundsSizeWidth), height: BorderHeight)
        pickerView.delegate = self
        pickerView.dataSource = self
        self.addSubview(pickerView)
        
        
        let topBgView = UIView()
        self.addSubview(topBgView)
        topBgView.frame = CGRect(x: 0, y: pickerView.frame.minY + 5, width: boundsSizeWidth, height: 40)
        topBgView.backgroundColor = .white
        
        
        lineView.frame = CGRect(x: 15, y: topBgView.bounds.height - 1, width: topBgView.bounds.width - 30, height: 1)
        lineView.backgroundColor = UIColor.systemGray
        topBgView.addSubview(lineView)
        
        cancelButton.frame = CGRect(x: 15, y: (topBgView.bounds.height - 20) / 2, width: 50, height: 20)
        cancelButton.setTitle("取消", for: .normal)
        cancelButton.setTitleColor(UIColor.system, for: .normal)
        cancelButton.titleLabel?.font = UIFont.systemFont(ofSize: 15)
        cancelButton.tag = 101
        cancelButton.addTarget(self, action: #selector(buttonClick), for: .touchUpInside)
        topBgView.addSubview(cancelButton)
        
        confirmButton.frame = CGRect(x: boundsSizeWidth - 50 - 15, y: cancelButton.frame.minY, width: 50, height: 20)
        confirmButton.setTitle("确定", for: .normal)
        confirmButton.setTitleColor(UIColor.system, for: .normal)
        confirmButton.titleLabel?.font = UIFont.systemFont(ofSize: 15)
        confirmButton.tag = 102
        confirmButton.addTarget(self, action: #selector(buttonClick), for: .touchUpInside)
        topBgView.addSubview(confirmButton)
        
        let titleViewX = cancelButton.frame.maxX + 15
        titleView.frame = CGRect(x: titleViewX, y: (topBgView.bounds.height - 20) / 2, width: confirmButton.frame.minX - 15 - titleViewX, height: 20)
        titleView.textColor = systemBlackColr
        titleView.textAlignment = .center
        titleView.font = UIFont.systemFont(ofSize: 15)
        titleView.text = "选择时间"
        topBgView.addSubview(titleView)
//        topBgView.backgroundColor = UIColor.red
        if bgView == nil {
            bgView = UIView(frame: CGRect(x: 0, y: 0, width: boundsSizeWidth, height: boundsSizeHeight - CGFloat(BorderHeight) + 5))
            bgView?.backgroundColor = .black
            bgView?.alpha = 0.011
            let tapGesture = UITapGestureRecognizer(target: self, action: #selector(dismiss))
            bgView?.addGestureRecognizer(tapGesture)
        }
        if bgView!.superview == nil {
            self.addSubview(bgView!)
        }
    }
    
    //MARK: 初始化数据
    private func initData()  {
        
        let addressPath:String = Bundle.main.path(forResource: "YYCity.json", ofType: nil)!
        let cityString:String = try! String(contentsOfFile: addressPath, encoding: String.Encoding.utf8)
        addressSource = changeJsonToArray(jsonString: cityString)
        let addressDic:NSDictionary = addressSource.firstObject as! NSDictionary
        let cityArr:NSArray = addressDic["cityList"] as! NSArray
        provinceResultModel.name = addressDic["name"] as? String
        provinceResultModel.code = addressDic["code"] as? String
        provinceResultModel.citylist = cityArr
        provinceResultModel.index = 0
        let cityDic:NSDictionary = cityArr.firstObject as! NSDictionary
        let areaArr:NSArray = cityDic["areaList"] as! NSArray
        cityResultModel.name = cityDic["name"] as? String
        cityResultModel.code = cityDic["code"] as? String
        cityResultModel.arealist = areaArr
        cityResultModel.index = 0
        let areaDic:NSDictionary = areaArr.firstObject as! NSDictionary
        areaResultModel.name = areaDic["name"] as? String
        areaResultModel.code = areaDic["code"] as? String
        areaResultModel.index = 0
            
        switch currentAddressPickerMode {
        case .YYAddressPickerModeArea:
            PickerColumnNumber = 3
            pickerView.selectRow(0, inComponent: 0, animated: true)
            pickerView.selectRow(0, inComponent: 1, animated: true)
            pickerView.selectRow(0, inComponent: 2, animated: true)
            self.pickerView.reloadAllComponents()
        case .YYAddressPickerModeCity:
            PickerColumnNumber = 2
            pickerView.selectRow(0, inComponent: 0, animated: true)
            pickerView.selectRow(0, inComponent: 1, animated: true)
            self.pickerView.reloadAllComponents()
        case .YYAddressPickerModeProvince:
            PickerColumnNumber = 1
            pickerView.selectRow(0, inComponent: 0, animated: true)
            self.pickerView.reloadAllComponents()
        }
        
        
        
        
        
        
    }
    
    //MARK: JSONString转换为数组【实例方法】
    /// 字符串转换为数组【实例方法】
    func changeJsonToArray(jsonString:String) ->NSArray{
        let jsonData:Data = jsonString.data(using: .utf8)!
        let array = try? JSONSerialization.jsonObject(with: jsonData, options: .mutableContainers)
        if array != nil {
            return array as! NSArray
        }
        return NSArray()
    }
    // MARK: 字符串转字典【实例方法】
    /// 字符串转字典【实例方法】
    func changeJsonToDictionary(_ str: String) -> [String : Any]?{
        let data = str.data(using: String.Encoding.utf8)
        if let dict = try? JSONSerialization.jsonObject(with: data!,
                        options: .mutableContainers) as? [String : Any] {
            return dict
        }

        return nil
    }
    
    /// 字符串转数组【类方法】
    class func changeJsonToArray(_ str: String) -> Array<Any>?{
        let data = str.data(using: String.Encoding.utf8)
        if let array = try? JSONSerialization.jsonObject(with: data!,
                                                        options: .mutableContainers) as? Array<Any> {
            return array
        }
        return nil
    }
    
    /// 字符串转字典【类方法】
    class func changeJsonToDictionary(_ str: String) -> [String : Any]?{
        let data = str.data(using: String.Encoding.utf8)
        if let dict = try? JSONSerialization.jsonObject(with: data!,
                        options: .mutableContainers) as? [String : Any] {
            return dict
        }
        return nil
    }
    
    //MARK: 按钮的响应事件
    @objc private func buttonClick(btn:UIButton){
        let tag:Int = btn.tag
        switch tag {
        case 101:
            dismissDatePickerView()
        case 102:
            dismissDatePickerView()
            if self.selectResultBlock != nil {
                let provinceModel:YYProvinceModel = provinceResultModel
                let cityModel:YYCityModel = cityResultModel
                let areaModel:YYAreaModel = areaResultModel
                self.selectResultBlock!(provinceModel, cityModel, areaModel)
            }
        default:
            break
        }
    }
    
    //MARK: UIPickerViewDataSource
    
    //返回UIPickerView当前的列数
    func numberOfComponents(in pickerView: UIPickerView) -> Int {
        return PickerColumnNumber
    }
    //确定每一列返回的东西
    func pickerView(_ pickerView: UIPickerView, numberOfRowsInComponent component: Int) -> Int {
        
        
        switch component {
        case 0:
            return addressSource.count
        case 1:
            return provinceResultModel.citylist.count
        case 2:
            return cityResultModel.arealist.count
        default:
            return 0
        }
    }
    //MARK: UIPickerViewDelegate
    
    //返回一个视图，用来设置pickerView的每行显示的内容。
    func pickerView(_ pickerView: UIPickerView, viewForRow row: Int, forComponent component: Int, reusing view: UIView?) -> UIView {
        let boundsSizeWidth = UIScreen.main.bounds.width
        let labelView = UILabel(frame: CGRect(x: boundsSizeWidth * CGFloat(component) / 6, y: 0, width: boundsSizeWidth / 6, height: 30))
        labelView.font = UIFont.systemFont(ofSize: 15)
        labelView.tag = component*100+row
        labelView.textAlignment = .center
        
        var width = boundsSizeWidth / 3 - 10
        switch currentAddressPickerMode {
        case .YYAddressPickerModeArea:
            width = boundsSizeWidth / 3 - 10
        case .YYAddressPickerModeCity:
            width = boundsSizeWidth / 2 - 10
        case .YYAddressPickerModeProvince:
            width = boundsSizeWidth - 10
        }
        width = width > maxWidth ? maxWidth : width
        labelView.frame = CGRect(x: 0, y: 0, width: width, height: 30)
//        if component == 0 && row == 5 {
//            labelView.backgroundColor = .brown
//        } else if component == 1 && row == 1 {
//            labelView.backgroundColor = .red
//        } else if component == 2 && row == 2 {
//            labelView.backgroundColor = .systemGray
//        } else if component == 3 && row == 3 {
//            labelView.backgroundColor = .systemRed
//        } else if component == 4 && row == 4 {
//            labelView.backgroundColor = .systemRed
//        } else if component == 5 && row == 5 {
//            labelView.backgroundColor = .systemRed
//        } else if component == 6 && row == 2 {
//            labelView.backgroundColor = .systemRed
//        }
        
        switch component {
        case 0:
            let addressDic:NSDictionary = addressSource[row] as! NSDictionary
            let provinceString:String = addressDic["name"] as! String
//            labelView.frame=CGRect(x:0, y:0,width:boundsSizeWidth/3.0 - 10, height:30)
            labelView.text = provinceString
        case 1:
//            labelView.frame=CGRect(x:0, y:0,width:boundsSizeWidth/3.0 - 10, height:30)
            let cityArr:NSArray = provinceResultModel.citylist
            let cityDic:NSDictionary = cityArr[row] as! NSDictionary
            let cityString:String = cityDic["name"] as! String
            labelView.text = cityString
        case 2:
//            labelView.frame=CGRect(x:0, y:0,width:boundsSizeWidth/3.0 - 10, height:30)
            let areaArr:NSArray = cityResultModel.arealist
            let areaDic:NSDictionary = areaArr[row] as! NSDictionary
            let areaString:String = areaDic["name"] as! String
            labelView.text = areaString
        default:
            labelView.text = ""
        }
        return labelView
    }
    
    
    //当点击UIPickerView的某一列中某一行的时候，就会调用这个方法
    func pickerView(_ pickerView: UIPickerView, didSelectRow row: Int, inComponent component: Int) {
        
        
        switch component {
        case 0:
            let provinceDic:NSDictionary = addressSource[row] as! NSDictionary
            provinceResultModel.name = provinceDic["name"] as? String
            provinceResultModel.code = provinceDic["code"] as? String
            provinceResultModel.citylist = provinceDic["cityList"] as? NSArray
            provinceResultModel.index = row
            
            
            let cityArr:NSArray = provinceResultModel.citylist
            guard cityArr.count > 0 else {
                return
            }
            let cityDic:NSDictionary = cityArr[0] as! NSDictionary
            cityResultModel.name = cityDic["name"] as? String
            cityResultModel.code = cityDic["code"] as? String
            cityResultModel.arealist = cityDic["areaList"] as? NSArray
            cityResultModel.index = 0
            switch currentAddressPickerMode {
            case .YYAddressPickerModeArea:
                pickerView.selectRow(0, inComponent: 1, animated: true)
                pickerView.selectRow(0, inComponent: 2, animated: true)
                self.pickerView.reloadComponent(1)
                self.pickerView.reloadComponent(2)
            case .YYAddressPickerModeCity:
                pickerView.selectRow(0, inComponent: 1, animated: true)
                self.pickerView.reloadComponent(1)
            case .YYAddressPickerModeProvince:
                break
            }
            
        case 1:
            let cityArr:NSArray = provinceResultModel.citylist
            let cityDic:NSDictionary = cityArr[row] as! NSDictionary
            cityResultModel.name = cityDic["name"] as? String
            cityResultModel.code = cityDic["code"] as? String
            cityResultModel.arealist = cityDic["areaList"] as? NSArray
            cityResultModel.index = row
            switch currentAddressPickerMode {
            case .YYAddressPickerModeArea:
                self.pickerView.reloadComponent(2)
            case .YYAddressPickerModeCity:
                break
            case .YYAddressPickerModeProvince:
                break
            }
            
        case 2:
            let areaArr:NSArray = cityResultModel.arealist
            let areaDic:NSDictionary = areaArr[row] as! NSDictionary
            areaResultModel.name = areaDic["name"] as? String
            areaResultModel.code = areaDic["code"] as? String
            areaResultModel.index = row
        default: break
            
        }
        
        
    }
    
    //MARK: 获取窗口window
    private func getWindow() ->UIWindow? {
        
        
        if let window:UIWindow = (UIApplication.shared.delegate?.window)! {
            return window
        }else{
            if #available(iOS 13.0, *) {
                let array:Set = UIApplication.shared.connectedScenes
                let windowScene:UIWindowScene = array.first as! UIWindowScene
                if let mainWindow:UIWindow = windowScene.value(forKeyPath:"delegate.window") as? UIWindow{
                    return mainWindow
                }else{
                    return UIApplication.shared.windows.first!
                }
            }else{
                return UIApplication.shared.keyWindow!
            }
        }
    }
    
    class private func getWindow() ->UIWindow? {
        
        return shared.getWindow()
    }
    
    class func showAddressPicker(mode:YYAddressPickerMode, title:String?, selectValue:String?, resultBlock:@escaping YYAddressResultBlock){
        if shared.superview == nil {
            getWindow()?.addSubview(shared)
        }
        print("currentAddressPickerMode = \(mode)")
        shared.titleView.text = title
        shared.initialDateString = selectValue ?? ""
        shared.currentAddressPickerMode = mode
        shared.initData()
        shared.selectResultBlock = resultBlock
    }
    
    private func dismissDatePickerView(){
        self.removeFromSuperview()
    }
    
    required init?(coder aDecoder: NSCoder) {
        super.init(coder: aDecoder)
        fatalError("init(coder:) has not been implemented")
    }

}
